/**
 * Created by chenweicheng on 7/3/2017.
 */
'use strict';

var ProtobufJsSupport = require('./ProtobufJsSupport');


var ProtoMessage = null;
var protobuf = require('react-native-rocks-protobufjs');
var count = 0;

class ProtobufJsManager {
    ifLogger = true;

    setLogger(ifLog) {
        this.ifLogger = ifLog
    }

    constructor() {

        this.loadProto().then((root) => {
            ProtoMessage = root;
            // console.log("load proto success")
        }, (error) => {
            // console.log("load proto fail=" + error)

        })
    }

    loadProto() {
        return new Promise((fulfill, reject) => {
            protobuf.load(this.getProto(), function (err, root) {
                if (err) {
                    reject(err)
                } else {
                    fulfill(root);
                }
            });
        });
    }

    createMessage(message, type) {
        return new Promise((fulfill, reject) => {
            let Message = this.getProtoMessage(type);
            let errMsg = Message.verify(message);
            if (errMsg) {
                reject(errMsg)
            }

            //将消息编码
            let buffer = Message.encode(message).finish();
            if (this.ifLogger) {
                // console.log('=============createMessage================')
                // console.log('encode buffer', buffer);
            }
            //将编码消息格式化成16进制字符串，各平台统一
            let hexStr = this.toHexStr(buffer);
            if (this.ifLogger) {
                // console.log('format encoded buffer to Hex', hexStr);
            }
            //添加自定义包头，包括是否超过20个字符和messageid
            // let headerStr = this.strAddHeader(hexStr, type);
            // if (this.ifLogger) {
            //     // console.log('add header hex', headerStr);//格式化后的16进制字符串例子：0008054001
            // }
            fulfill(hexStr)


        });
    }


    toHexStr(buffer) {
        let string = "";
        for (let i = 0; i < buffer.length; i++) {
            // console.log("The number is： " + buffer[i].toString(16));
            string = string + this.formatStr(buffer[i].toString(16));
        }
        return string;
    }

    formatStr(str) {
        if (str.length == 1) {
            return "0" + str
        } else {
            return str
        }
    }


    strAddHeader(str, headerType) {
        if (this.ifLogger) {
            // console.log('=============addHeader================')
            // console.log("HeaderType=", headerType);
            // console.log("Hex str to add header", str)
        }

        return str.length > 40 ? "1" + headerType + str : "0" + headerType + str;
    }

    getMessageId(str) {
        if (this.ifLogger) {
            // console.log('=============getMessageId================')
            // console.log("MessageId=" + str.substr(1, 1))
        }
        return str.substr(1, 1)
    }

    parseMessage(oriStr, type) {
        return new Promise((fulfill, reject) => {
            if (this.ifLogger) {
                // console.log('=============parseMessage================');
                // console.log("before sub header=", oriStr);
            }
            // let string = oriStr.substr(2);
            if (this.ifLogger) {
                // console.log("after sub header=", string);
            }
            //将16进制字符串反格式化为编码消息
            let y = new Uint8Array(oriStr.length / 2);
            for (let i = 0; i < oriStr.length / 2; i++) {
                y[i] = parseInt(oriStr.substring(i * 2, (i + 1) * 2), 16);
            }


            let TypeMessage = this.getProtoMessage(type);
            //解析编码消息
            let message = TypeMessage.decode(y);


            // console.log('Parse Result', message);
            let errMsg = TypeMessage.verify(message);
            // console.log("errMsg===============" + errMsg)
            if (errMsg) {
                reject(errMsg)
            } else {
                fulfill(message)
            }

        })
        // var test = ProtoMessage.lookup('myProto.ToothbrushMessage')
        // test.decode(y)

        // return message;

    }

    getLoopCount() {

        return parseInt(count == 127 ? 1 : ++count);
    }

    getProtoMessage(messageId) {

        return ProtoMessage.lookup(this.getParseMessageName(messageId))
    }

    getParseMessageName = ProtobufJsSupport.getParseMessageName;

    headerType = ProtobufJsSupport.headerType;

    getProto = ProtobufJsSupport.getProto
}


module.exports = new ProtobufJsManager();